import React, {
  useCallback,
  useEffect,
  useState,
  useRef,
  useImperativeHandle,
} from "react";
import { DownOutlined, UpOutlined } from "@ant-design/icons";
import { Form, Table, Button, Divider, Row, Col } from "antd";
import useTableData from "@/hooks/useTableData";
import style from "./baseFormTable.module.scss";
const onLineHeight = 40;
// const outLineBtnHeight = 31;
const BaseFormTable = (
  {
    children,
    formOtherConfig = {},
    tableOtherConfig = {},
    queryApiAndOtherParams,
  },
  ref
) => {
  // table相关
  // 由于别的组件state改变，导致BaseFormTable组件刷新，参数地址改变，缓存起来
  const [queryApiAndOtherParamsState] = useState(queryApiAndOtherParams);
  const [
    current,
    setCurrentPage,
    pageSize,
    setPageSize,
    ,
    setQueryForm,
    dataSource,
    total,
  ] = useTableData({
    queryApiAndOtherParams: queryApiAndOtherParamsState,
    initMaxResult: 2,
  });
  // form 相关
  const [showMoreFormItem, setShowMoreFormItem] = useState(false);
  const [isSlotRowInputOverHeight, setIsSlotRowInputOverHeight] = useState(0);
  const [isValidTrue, setIsValidTrue] = useState(true);
  const [formValues, setFormValues] = useState({});
  const slotRowInput = useRef(null);
  const [form] = Form.useForm();

  const formInstance = formOtherConfig.form || form;

  // 函数组件，使用useImperativeHandle来暴露给父组件属性及方法
  useImperativeHandle(ref, () => ({
    refresh: () => setCurrentPage(current),
  }));

  // form 相关
  const findOndChildByKey = useCallback(
    (key) => {
      if (!children) return null;
      if (Array.isArray(children))
        return children.find((item) => item.key === key);
      else return children.key === key && children;
    },
    [children]
  );

  // 点击“搜索”按钮，表单验证成功后，设置表单值
  const onFinish = useCallback(
    (values) => {
      setFormValues(values);
      setQueryForm(values);
    },
    [setQueryForm]
  );

  // 表单验证失败时
  const onFinishFailed = useCallback(
    ({ values }) => {
      setFormValues(values);
      setIsValidTrue(false);
      if (isSlotRowInputOverHeight > onLineHeight) {
        setShowMoreFormItem(true);
      }
    },
    [isSlotRowInputOverHeight]
  );

  // 重置表单
  const resetFrom = useCallback(() => {
    formInstance.resetFields();
    setQueryForm({});
  }, [formInstance, setQueryForm]);

  // “更多搜索”按钮点击功能
  const moreFormBtnClick = useCallback(() => {
    setShowMoreFormItem(!showMoreFormItem);
    if (!isValidTrue) {
      formInstance.resetFields();
      setIsValidTrue(true);
      formInstance.setFieldsValue(formValues);
    }
  }, [formInstance, formValues, isValidTrue, showMoreFormItem]);

  // 获取第一次挂载form列表时slotRowInput的高度，只获取一次作为初始值
  const getslotRowInputHeight = useCallback(() => {
    // 一行默认40px高度，当超过40px，则"更多搜索"打开
    setIsSlotRowInputOverHeight(slotRowInput.current.offsetHeight);
  }, []);

  useEffect(() => {
    findOndChildByKey("form") && getslotRowInputHeight();
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, []);

  // 创建“更多搜索”按钮
  const creatMoreBtn = useCallback(() => {
    return isSlotRowInputOverHeight > onLineHeight ? (
      <Divider className={style.dividerContainer}>
        <span className={style.hoverPoint} onClick={moreFormBtnClick}>
          更多搜索{showMoreFormItem ? <UpOutlined /> : <DownOutlined />}
        </span>
      </Divider>
    ) : null;
  }, [isSlotRowInputOverHeight, moreFormBtnClick, showMoreFormItem]);

  // 创建“重置”、“搜索”按钮
  const creatFormBtn = useCallback(
    (type) => {
      const isHidden =
        (type === "oneLine" && showMoreFormItem) ||
        (type === "outLine" &&
          (!(isSlotRowInputOverHeight > onLineHeight) || !showMoreFormItem));

      return (
        <div
          className={[
            style.rightBtn,
            isHidden ? style.hiddenBtn : "",
            type === "outLine" && isHidden ? style.noneBtn : "",
          ].join(" ")}
        >
          <Button type="ghost" onClick={resetFrom} className={style.formBtn}>
            重置
          </Button>
          <Button type="primary" htmlType="submit" className={style.formBtn}>
            搜索
          </Button>
        </div>
      );
    },
    [resetFrom, showMoreFormItem, isSlotRowInputOverHeight]
  );

  // table相关
  const onChange = useCallback(
    (current, pageSize) => {
      setCurrentPage(current);
      setPageSize(pageSize);
    },
    [setCurrentPage, setPageSize]
  );

  return (
    <React.Fragment>
      {findOndChildByKey("form") && (
        <Form
          form={form}
          onFinish={onFinish}
          onFinishFailed={onFinishFailed}
          labelCol={{ span: 8 }}
          wrapperCol={{ span: 15 }}
          {...formOtherConfig}
        >
          <div className={style.baseForm}>
            <Row
              ref={slotRowInput}
              className={[
                style.slotRowInput,
                isSlotRowInputOverHeight > onLineHeight && !showMoreFormItem
                  ? style.oneLineInput
                  : "",
              ].join(" ")}
              // style={{
              //   height: showMoreFormItem
              //     ? isSlotRowInputOverHeight + outLineBtnHeight + "px"
              //     : "unset",
              // }}
            >
              {findOndChildByKey("form")}
              <Col span={24} className={style.slotRowBtn}>
                {creatFormBtn("outLine")}
              </Col>
            </Row>
            {creatFormBtn("oneLine")}
          </div>
          {creatMoreBtn()}
        </Form>
      )}
      <Table
        {...tableOtherConfig}
        dataSource={
          (dataSource.length && dataSource) || tableOtherConfig.dataSource
        }
        pagination={{ current, pageSize, total, onChange }}
      />
    </React.Fragment>
  );
};

export default React.memo(
  React.forwardRef(BaseFormTable),
  (prevProps, nextProps) => {
    /*
  如果把 nextProps 传入 render 方法的返回结果与
  将 prevProps 传入 render 方法的返回结果一致则返回 true，
  否则返回 false
  */
  }
);
